﻿using System;
using System.Collections.Generic;
using System.IO;
using System.Text;

namespace Safebrowsing
{
    /// <summary>
    /// Response for request for data.
    /// </summary>
    public class DataResponse
    {
        /// <summary>
        /// Creates an instance of the data response from the response bytes
        /// TODO: Catch and handle exceptions
        /// </summary>
        public DataResponse(byte[] data)
        {
            DataLists = new List<DataListResponse>();

            using (Stream stream = new MemoryStream(data) {Position = 0})
            {
                DataListResponse dataListResponse = null;
                string line = Utils.ReadLine(stream);
                while (!string.IsNullOrEmpty(line))
                {
                    if (line.StartsWith(Constants.MARK_MIN_DELAY))
                    {
                        MinDelay = Utils.ToInt(line.Substring(Constants.MARK_MIN_DELAY.Length).Trim(), 0);
                    }
                    else if (line.StartsWith(Constants.MARK_LIST_NAME))
                    {
                        string listName = line.Substring(Constants.MARK_LIST_NAME.Length).Trim();
                        if (dataListResponse != null) DataLists.Add(dataListResponse);
                        dataListResponse = new DataListResponse(listName);
                    }
                    else if (line.StartsWith(Constants.MARK_ADDDEL))
                    {
                        List<int> addDel = Utils.SplitRangeList(line.Substring(Constants.MARK_ADDDEL.Length));
                        if (dataListResponse != null) dataListResponse.AddChunksToDelete.AddRange(addDel);
                    }
                    else if (line.StartsWith(Constants.MARK_SUBDEL))
                    {
                        List<int> subDel = Utils.SplitRangeList(line.Substring(Constants.MARK_SUBDEL.Length));
                        if (dataListResponse != null) dataListResponse.SubChunksToDelete.AddRange(subDel);
                    }
                    else if (line.StartsWith(Constants.MARK_REDIRECT_URL))
                    {
                        string redirectUrl = line.Substring(Constants.MARK_REDIRECT_URL.Length);
                        if (dataListResponse != null) dataListResponse.RedirectUrls.Add(new Uri(Constants.PROTOCOL + "://" + redirectUrl));
                    }
                    else if (line.StartsWith(Constants.MARK_RESET))
                    {
                        Reset = true;
                        return;
                    }
                    line = Utils.ReadLine(stream);
                }
                if (dataListResponse != null)
                {
                    DataLists.Add(dataListResponse);
                }
            }
        }

        /// <summary>
        /// Minimum delay before polling again in seconds
        /// </summary>
        public int MinDelay { get; set; }

        /// <summary>
        /// If server returns "r:pleasereset" -- we should clear out all current data int the database before requesting again
        /// </summary>
        public bool Reset { get; set; }

        /// <summary>
        /// Collection of the list responses
        /// </summary>
        public List<DataListResponse> DataLists { get; set; }

        public override string ToString()
        {
            var sb = new StringBuilder();
            sb.AppendFormat("Minimum delay: {0} seconds", MinDelay);
            sb.AppendLine();
            if (Reset)
            {
                sb.AppendLine("Reset all data");
                return sb.ToString();
            }
            sb.AppendLine();
            foreach (DataListResponse response in DataLists)
            {
                sb.AppendLine(response.ToString());
                sb.AppendLine();
            }
            return sb.ToString();
        }
    }
}